import axios from "axios";
import NProgress from "nprogress";
import { Message } from "element-ui";
import { getCookie } from "@xingyuelongchen/vue3-storage";
import vuex from '../store';
import router from "@/router";
const CancelToken = axios.CancelToken;
let axiosRequestList = [];
let messageNotice = null;
NProgress.configure({
  easing: "ease",
  speed: 500,
  showSpinner: true
});
const errorMessage = {
  400: "请求错误",
  401: "暂无权限，请重新登录！",
  404: '资源不存在',
  500: "服务器错误",
  502: "服务器错误"
};
const removePending = (config) => {
  NProgress.done();
  let index = axiosRequestList.findIndex(e => e.url === axios.defaults.baseURL + config.url);
  if (index > 0) {
    axiosRequestList[index].cancel();
    axiosRequestList.splice(index, 1);
  }
};
export const downloadFile = (res, filename = "") => {
  let blob = new Blob([res.data], { type: res.config.responseType });
  let downloadElement = document.createElement("a");
  let href = window.URL.createObjectURL(blob);
  downloadElement.href = href;
  let fileName = filename || res.headers["content-disposition"].match(/(?<=\=).*/g);
  downloadElement.download = fileName.length ? decodeURIComponent(fileName[0]) : "未命名";
  document.body.appendChild(downloadElement);
  downloadElement.click();
  document.body.removeChild(downloadElement);
  window.URL.revokeObjectURL(href);
};
const request = (config) => {
  // removePending(config); 放在这里是取消掉上一次的请求
  if (!config.removePending) config.cancelToken = new CancelToken((c) => {
    axiosRequestList.unshift({
      url: axios.defaults.baseURL + config.url,
      cancel: c
    });
  });
  // 放这里是取消本次请求，上次请求继续完成
  removePending(config);
  NProgress.start();
  if (getCookie("token")) config.headers.token = getCookie("token");
  let params = config.params || {};
  let obj = {};
  Object.keys(params).forEach(e => {
    if (![null, undefined, ''].includes(params[e])) obj[e] = params[e]
  })
  config.params = obj;
  return config;
};
// 请求错误
const requestError = (err) => {
  let { config = {} } = err;
  removePending(config);
  return Promise.reject(err);
};
// 响应体
const response = (res) => {
  let { data, config, status } = res;
  removePending(config);
  if (status === 200) {
    if (["blob", "arraybuffer"].includes(config.responseType)) {
      downloadFile(res); return res;
    }
    if (config.responseType === "text") return res;
    if (data?.message) {
      messageNotice && messageNotice.close();
      if (data.code === 200) messageNotice = Message.success(data.message);
      else messageNotice = Message.error(data.message);
    }
    if (data.code === 200) return res;
    if (data.code === 401) router.replace('/login')
  }
  return Promise.reject(res);
};
// 响应错误
const responseError = (err) => {
  let { config = {}, response = null } = err;
  removePending(config);
  // console.log(config);
  if (response && response.status) {
    messageNotice && messageNotice.close();
    messageNotice = Message.error(errorMessage[response.status] || response.statusText);
    if (response.status === 401) vuex.dispatch('logout');
  }
  return Promise.reject(err);
};
axios.defaults.baseURL = process.env.VUE_APP_BASE_API || "";
axios.defaults.timeout = process.env.VUE_APP_TIMEOUT || 10000;
axios.defaults.crossDomain = true;
axios.defaults.withCredentials = true;
axios.defaults.method = "get";
axios.defaults.headers.common["Accept-Language"] = "zh-cn";
axios.interceptors.request.use(request, requestError);
axios.interceptors.response.use(response, responseError);
export default axios;


